/*
 * DvmDex.h
 *
 *  Created on: 2011-7-9
 *      Author: gexiao
 */
/*
 * The VM wraps some additional data structures around the DexFile. These
 * are defined here.
 */
#ifndef DVMDEX_H_
#define DVMDEX_H_
#include "../libdex/DexFile.h"
#include "AtomicCache.h"

//extern
struct ClassObject;
struct HashTable;
struct InstField;
struct Method;
struct StringObject;

/*
 * Some additional VM data structures that are associated with the DEX file.
 */
typedef struct DvmDex {
	//pointer to the DexFile we're associated with
	DexFile* pDexFile;

	//clone of pDexFile->pHeader (it's used frequently enough)
	const DexHeader* pHeader;

	//interned strings;parallel to "stringIds"
	struct StringObject** pResStrings;

	//resolved classes; parallel to "typeIds"
	struct ClassObject** pResClasses;

	//resolved methods; parallel to "methodIds"
	struct Method** pResMethods;

	/*
	 * resolved instance fields; parallel to fieldIds
	 * (this holds both InstField and StaticField)
	 */
	struct Field** pResFields;

	//interface method lookup cache
	struct AtomicCache* pInterfaceCache;

	//shared memory region with file contents
	MemMapping memMap;
} DvmDex;

/*
 * Given a file descriptor for an open "optimized" DEX file,map it into
 * memory and parse the contents.
 *
 * On success, returns 0 and sets "*ppDvmDex" to a newly-allocated DvmDex.
 * On failure, returns a meaningful error code [currently just -1].
 */
int dvmDexFileOpenFromFd(int fd, DvmDex** ppDvmDex);

/*
 * Free a DvmDex structure, along with any associated structures.
 */
void dvmDexFileFree(DvmDex* pDvmDex);

/*
 * Return the requested item if it has been resolved, or NULL if it hasn't.
 */
INLINE struct StringObject* dvmDexGetResolvedString(const DvmDex* pDvmDex,
		u4 stringIdx) {

}

INLINE struct ClassObject* dvmDexGetResolvedClass(const DvmDex* pDvmDex,
		u4 classIdx) {
	assert(classIdx < pDvmDex->pHeader->typeIdsSize);
	return pDvmDex->pResClasses[classIdx];
}

INLINE struct Method* dvmDexGetResolvedMethod(const DvmDex* pDvmDex,
		u4 methodId) {

}

INLINE struct Field* dvmDexGetResolvedField(const DvmDex* pDvmDex, u4 fieldIdx) {

}

/*
 * Update the resolved item table. Resolution always produces the same
 * result, so we're not worried about atomicity here.
 */
INLINE void dvmDexSetResolvedClass(DvmDex* pDvmDex, u4 classIdx,
		struct ClassObject* clazz) {
	assert(classIdx<pDvmDex->pHeader->typeIdsSize);
	pDvmDex->pResClasses[classIdx] = clazz;
}

#endif /* DVMDEX_H_ */
